package com.neu.yth.nepBackend.aqiFeedback.service.impl;


import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.neu.yth.nepBackend.aqiFeedback.mapper.AqiFeedbackMapper;
import com.neu.yth.nepBackend.aqiFeedback.service.IAqiFeedbackService;
import com.neu.yth.nepBackend.entity.AqiFeedback;
import com.neu.yth.nepBackend.entity.Grid;
import com.neu.yth.nepBackend.entity.Member;
import com.neu.yth.nepBackend.enums.ResponseEnum;
import com.neu.yth.nepBackend.utils.Result;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.interceptor.TransactionAspectSupport;
import org.springframework.web.reactive.function.client.WebClient;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.List;

/**
 * <p>
 * 空气质量公众监督反馈表 服务实现类
 * </p>
 *
 * @author YTH
 * @since 2024-05-31
 */
@Service
@Slf4j
public class AqiFeedbackServiceImpl extends ServiceImpl<AqiFeedbackMapper, AqiFeedback> implements IAqiFeedbackService {

    @Autowired
    private AqiFeedbackMapper aqiFeedbackMapper;

    @Autowired
    private WebClient webClient;

    /**
     * 插入空气质量公众监督反馈表
     *
     * @param aqiFeedback
     * @param token
     * @return
     */
    @Override
    public Result insertAqiAf(AqiFeedback aqiFeedback, String token) {
        Calendar calendar = Calendar.getInstance();
        aqiFeedback.setAfDate(calendar.getTime());
        //0未指派
        aqiFeedback.setState(0);
        int count = aqiFeedbackMapper.insert(aqiFeedback);

        if (count == 1) {
            Integer gmId = autoAssign(aqiFeedback);
            if (gmId != null) {
                aqiFeedback.setGmId(gmId);
                Result res = this.assign(aqiFeedback, token);
                if (res.getCode() == 200) {
                    return Result.success(aqiFeedback);
                } else {
                    return Result.fail(200, "尚未分配网格员", null);
                }
            } else {
                return Result.fail(200, "尚未分配网格员", null);
            }
        } else {
            return Result.fail(ResponseEnum.INSERT_FAILED);
        }
    }

    /**
     * 自动分配
     *
     * @param aqiFeedback
     * @return
     */
    public Integer autoAssign(AqiFeedback aqiFeedback) {
        Result result = webClient.get()
                .uri("/member/select/autoAssign?location={location}", aqiFeedback.getProvince())
                .retrieve()
                .bodyToMono(Result.class)
                .block();
        if (result.getCode() == 200) {
            return (Integer) result.getResult();
        }

        return null;
    }


    /**
     * 更新空气质量公众监督反馈表
     *
     * @param aqiFeedback
     * @return
     */
    @Override
    @Transactional
    public Result updateAqiAf(AqiFeedback aqiFeedback, String token) {
        AqiFeedback aqi = aqiFeedbackMapper.selectById(aqiFeedback.getAfId());
        if (aqi == null) {
            return Result.fail(ResponseEnum.UPDATE_ID_NOT_EXIST);
        }
        boolean flag = this.updateById(aqiFeedback);
        if (flag) {
            //网格员是否空闲
            LambdaQueryWrapper<AqiFeedback> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(AqiFeedback::getGmId, aqi.getGmId());
            queryWrapper.eq(AqiFeedback::getState, 1);
            Long count = aqiFeedbackMapper.selectCount(queryWrapper);
            if (count == 0) {
                Member member = new Member();
                member.setMemId(aqi.getGmId());
                member.setMemState(1);
                Result res = webClient.put()
                        .uri("/member/update")
                        .header("Authorization", token)
                        .bodyValue(member)
                        .retrieve()
                        .bodyToMono(Result.class)
                        .block();
                if (res.getCode() == 200) {
                    return Result.success(aqiFeedback);
                } else {
                    TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                    return Result.fail(ResponseEnum.UPDATE_FAILED);
                }
            }
            return Result.success(aqiFeedback);
        } else {
            return Result.fail(ResponseEnum.UPDATE_FAILED);
        }
    }

    /**
     * 根据id查询空气质量公众监督反馈表
     *
     * @param id
     * @return
     */
    @Override
    public Result selectById(Integer id) {
        LambdaQueryWrapper<AqiFeedback> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(AqiFeedback::getMemId, id);
        List<AqiFeedback> aqiFeedbacks = aqiFeedbackMapper.selectList(queryWrapper);
        if (aqiFeedbacks == null) {
            return Result.fail(ResponseEnum.SELECT_FAILED);
        } else if (aqiFeedbacks.size() == 0) {
            return Result.fail(ResponseEnum.SELECT_AQIFB_NOT_EXIST);
        }
        return Result.success(aqiFeedbacks);
    }

    /**
     * 查询所有空气质量公众监督反馈表
     *
     * @return
     */
    @Override
    public Result selectAll() {
        LambdaQueryWrapper<AqiFeedback> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.ne(AqiFeedback::getState, 0);
        List<AqiFeedback> aqiFeedbacks = aqiFeedbackMapper.selectList(queryWrapper);
        if (aqiFeedbacks == null) {
            return Result.fail(ResponseEnum.SELECT_FAILED);
        }
        return Result.success(aqiFeedbacks);
    }

    /**
     * 查询未分配的空气质量公众监督反馈表
     *
     * @return
     */
    @Override
    public Result selectUnAssigned() {
        LambdaQueryWrapper<AqiFeedback> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(AqiFeedback::getState, 0);
        List<AqiFeedback> aqiFeedbacks = aqiFeedbackMapper.selectList(queryWrapper);
        if (aqiFeedbacks == null) {
            return Result.fail(ResponseEnum.SELECT_FAILED);
        }
        return Result.success(aqiFeedbacks);
    }

    /**
     * 分配空气质量公众监督反馈表
     *
     * @param aqiFeedback
     * @return
     */
    @Override
    @Transactional
    public Result assign(AqiFeedback aqiFeedback, String token) {
        Result result = webClient.get()
                .uri("/member/update/assign/{memId}", aqiFeedback.getGmId())
                .header("Authorization", token)
                .retrieve()
                .bodyToMono(Result.class)
                .block();
        if (result.getCode() == 200) {
            aqiFeedback.setState(1);
            aqiFeedback.setAssignDate(Calendar.getInstance().getTime());
            int count = aqiFeedbackMapper.updateById(aqiFeedback);
            if (count == 1) {
                return Result.success(aqiFeedback);
            }
            return Result.fail(ResponseEnum.ASSIGN_FAILED);
        }
        TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
        return result;
    }

    /**
     * 分配(test)
     *
     * @param afId
     * @param gmId
     * @return
     */
    @Override
    public Result assignMember(Integer afId, Integer gmId, String token) {
        Result result = webClient.get()
                .uri("/member/update/assign/{memId}", gmId)
                .header("Authorization", token)
                .retrieve()
                .bodyToMono(Result.class)
                .block();
        return result;
    }

    /**
     * 查询我的未分配的空气质量公众监督反馈表
     *
     * @return
     */
    @Override
    public Result selectMyUnAssigned(Integer gmId, Integer state) {
        LambdaQueryWrapper<AqiFeedback> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(AqiFeedback::getState, state);
        queryWrapper.eq(AqiFeedback::getGmId, gmId);
        List<AqiFeedback> aqiFeedbacks = aqiFeedbackMapper.selectList(queryWrapper);
        if (aqiFeedbacks == null) {
            return Result.fail(ResponseEnum.SELECT_FAILED);
        }
        return Result.success(aqiFeedbacks);
    }

    /**
     * 查询未分配的空气质量公众监督反馈表数量
     *
     * @return
     */
    @Override
    public Result selectCount() {
        return Result.success(aqiFeedbackMapper.selectCount(null));
    }

    /**
     * 查各个省份数据
     *
     * @param provinces
     * @return
     */
    @Override
    public Result selectCountProvince(List<String> provinces) {
        if (provinces == null || provinces.size() == 0) {
            return Result.fail(ResponseEnum.PARAM_IS_NULL);
        }
        List<Grid> grid = new ArrayList<>();
        log.info("grid:" + provinces);
        for (String name :
                provinces) {
            log.info("name:" + name);
            Grid child = new Grid();
            child.setGname(name);
            LambdaQueryWrapper<AqiFeedback> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.like(AqiFeedback::getProvince, name);
            child.setCount(aqiFeedbackMapper.selectCount(queryWrapper));
            grid.add(child);
        }
        return Result.success(grid);
    }
}
